home *** CD-ROM | disk | FTP | other *** search
- /*
- #-------------------------------------------------------------------------------------------
- #
- # Program: < DMZ 1.3 >
- # File: < dmzAT.c >
- #
- # by Pete Helme
- # of <Apple Macintosh Developer Technical Support - or wheverever>
- #
- # Modification History
- # 5/23/94 rrk Implemented Steve Falkenburg's changes for compatibility with PPC
- # This code was compile with MPW 3.3.1 and Think C 7.0 using
- # Universal headers
- # 9/20/92 rrk Change nbp type from "\pnot Anything" to "\pEcho Type". Set socket
- # address to 4 as opposed to leaving it at 0.
- # 3/25/92 rrk Fixed program so that if no zones are selected and the "no zones (*)"
- # item selected, the local zone is searched.
- # 3/25/92 rrk Implemented J. Luther's socket listener, replacing Pete's listener
- # 3/25/92 rrk Updated code to work with Think C 5.0.
- #
- # Copyright © 1990 Apple Computer, Inc.
- # All rights reserved.
- #
- #-------------------------------------------------------------------------------------------
- */
-
- /*
- * dmz Sample AppleTalk Stuff
- *
- * This unit handles all AppleTalk functions for dmz. Including: AppleTalk
- * presence verification and activation, socket opening, set self send enabling
- * name binding protocol registration, bridge presence verification,
- * zone name lookups, hot dish zapper, name removal, socket closing & no weeds.
- *
- */
-
- #include "dmz.h"
-
-
- /* globals from afar */
- /* out main dialog */
- extern DialogPtr gLookupDialog;
- extern DialogPtr gMyDialog;
- extern char gNameGlob[34];
- extern SysEnvRec GMAC;
- extern myATQEntry gATQEntry;
- extern short gATalkFlags;
-
- /* and others */
- /*
- * gBuffers is used in the by the socket listener code set up in the doEcho
- * function. The socket listener uses these buffers to save received packets
- * until they can be processed.
- */
- PacketBuffer gBuffers[kNumBuffers]; /* set up by InitEchoBuffers */
-
- /*
- * gFreeQ and gUsedQ as their names imply, are used to track whether gBuffers
- * packet record buffers are available for use or have been filled in by the
- * socket listener and are available for processing.
- */
- QHdr gFreeQ, gUsedQ; /* set up by InitEchoBuffers */
- Handle gSockCodeHndl = nil; /* handle to socket listener code resource */
-
-
- Ptr gBuffPtr = nil;
- myMPPParamBlock *gPBLkUP = nil;
- Boolean gUpdateListFlag;
- Boolean gLookupFinished;
- NamesTableEntry gMyNTE;
- AddrBlock gTheBridgeAddress;
- Boolean gHasPhase2 = false;
- NamesTableEntry gLookupNTE;
- char gOrigSelfSend;
-
- Ptr GTHEVBLPTR;
- Ptr GTHETASKPTR;
-
- /*
- * Inline routines for saving & restoring A5 in our PLookupName completion routine.
- *
- * move.l a5, -(a7)
- * move.l $FFFC(a0), a5 ; -4(A0)
- *
- */
- #ifndef powerc
- pascal void saveThatA5(void)
- = {0x2f0d, 0x2a68, 0xFFFC};
- #endif
-
- /*
- * move.l (a7)+, a5
- */
- #ifndef powerc
- pascal void restoreThatA5(void)
- = {0x2A5F};
- #endif
-
-
- /*
- * Boring Pascal string concat routine. Skip ahead a bit.
- */
- unsigned char *Pstrcat(unsigned char *s, unsigned char *t)
- {
- long i, length;
- unsigned char *p;
-
- length = *t;
- p = s + *s + 1;
- t++;
-
- for(i=0;i<length;i++)
- *p++ = *t++;
-
- *s += length;
- return s;
- }
-
- /*
- * Returns length of pascal type strings. Again, quite boring.
- */
- unsigned char PStrLen(unsigned char *e)
- {
- unsigned char length;
-
- length = *e;
- return(length);
- }
-
- /*
- * Returns true if two Pascal strings are the same, false otherwise.
- */
-
- Boolean PStrComp(unsigned char *str1, unsigned char *str2)
-
- {
- unsigned char i;
- unsigned char j;
- Boolean ok;
-
- if (*str1 != *str2)
- return(false); /* strings are of unequal length */
-
- i = *str1;
- ok = true; /* assume strings are the same */
- j = 0;
- for (j = 0; j < i; j++) {
- if (*(++str1) != *(++str2))
- return(false);
- }
- return(true);
- }
-
- /*
- * Removes a specific NBP Lookup from queue if one pending. Why? So we don't hurt ourselves.
- *
- */
- void killLookups(void)
- {
- MPPParamBlock killPB;
- OSErr resultCode;
-
- if(gPBLkUP->myMPP.MPPioResult == 1) {
- killPB.NBPnKillQEl = (Ptr)&gPBLkUP->myMPP.MPP.qLink;
- resultCode = PKillNBP(&killPB, false);
- }
- }
-
- /*
- * Removes our name and ATP socket.
- */
- void removeMyNameAndSocket(void)
- {
- MPPParamBlock pb;
-
- if (TstNameRegisteredFlag(gATalkFlags))
- {
- if (OpenTransportActive())
- {
- OTDeleteMyName();
- // dont clear the kNameRegistered flag here since it will get cleared by the Mapper Handler
- }
- else
- {
- pb.NBPentityPtr = (Ptr)&gMyNTE.nt.entityData[0];
- PRemoveName(&pb, false);
- ClrNameRegisteredFlag(gATalkFlags);
- }
- }
- }
-
- /*
- * Shutdown our AppleTalk usage. Disposes of name lookup buffers.
- * Calls to remove our NBP name.
- */
- void closeUpOurAppleTalk(void)
- {
- Size listenerSize;
-
- killLookups();
- if (OpenTransportActive())
- CleanupOTServices();
-
- if(gBuffPtr != 0L)
- DisposePtr(gBuffPtr);
- if(gPBLkUP != 0L)
- DisposePtr((Ptr) gPBLkUP);
-
- if (TstSocketBuffsHeldFlag(gATalkFlags)) /* ckeck if socket buffer held due to VM */
- {
- UnholdMemory(&gBuffers, sizeof(gBuffers));
- UnholdMemory(&gFreeQ, sizeof(QHdr));
- UnholdMemory(&gUsedQ, sizeof(QHdr));
- ClrSocketBuffsHeldFlag(gATalkFlags);
- }
-
- if (TstListenerHeldFlag(gATalkFlags)) /* ckeck if socket listener held due to VM */
- {
- listenerSize = GetHandleSize(gSockCodeHndl);
- UnholdMemory(*gSockCodeHndl, listenerSize);
- ClrListenerHeldFlag(gATalkFlags);
- }
-
- if (TstATQInstalledFlag(gATalkFlags)) /* check if ATalk Trans queue installed */
- {
- LAPRmvATQ((ATQEntry*)&gATQEntry);
- ClrATQInstalledFlag(gATalkFlags);
- }
-
- removeMyNameAndSocket();
- }
-
- /*
- * Registers name from the System's STR -16413, the Flagship (Macintosh Name) resource under
- System 7.x (what appears in the Sharing Setup control panel), or STR -16096 resource if
- under System 6.0.x. (what is usually seen in the Chooser)
- */
-
- void registerMyName()
- {
- MPPParamBlock pb;
- OSErr err;
- long byteCount;
- StringHandle userName;
-
- if (OpenTransportActive())
- OTRegisterMyName();
- else
- {
- byteCount = 0L;
-
- /* this grabs the name from the Macintosh Name String if it is found under System 7.x
- or the user's Chooser name string if 6.0.x or earlier. If there is nothing
- there we'll substitute our own name */
- userName = GetString(kFlagshipNameResourceID);
- if (**userName == 0)
- {
- userName = GetString(kMachineNameResourceID);
- if(**userName == 0)
- {
- userName = (StringHandle)NewHandle(sizeof(Str32));
- if (userName)
- BlockMove("\pYour name here", *userName, 15L);
- else
- userName = nil;
- }
- }
- if (userName)
- {
- NBPSetNTE((Ptr)&gMyNTE, (ConstStr32Param)*userName, (ConstStr32Param)kEchoType, (ConstStr32Param)"\p*", gMyNTE.nt.nteAddress.aSocket);
-
- pb.NBPinterval = 2;
- pb.NBPcount = 3;
-
- /* wants pointer to NamesTableEntry NOT entityName! */
- pb.NBPntQElPtr = (Ptr)&gMyNTE;
- pb.NBPverifyFlag = 1; /* verify that we be the only one! */
-
- err = PRegisterName(&pb, false);
- if (err == noErr)
- {
- SetNameRegisteredFlag(gATalkFlags);
- ((dmzEntryPtr) *(gATQEntry.globs))->dmzNTEPtr = &gMyNTE;
- }
- /* if error occured registering name, there is no reason to
- * abort the program
- */
- }
- // if the handle couldn't be allocated, go ahead anyway.
- }
- }
-
-
- /*
- * Enables AppleTalk option to talk to one's own node. ONLY for SE's, //'s or MacPluses with AppleTalk driver of v48 or greater!!
- * Saves original state in the global gOrigSelfSend.
- */
- void enableSetSelfSend()
- {
-
- SetSelfparms pb;
- OSErr err;
-
- pb.newSelfFlag = true; /* set self send option */
- err = PSetSelfSend((MPPPBPtr) &pb, false);
- if (err == noErr)
- gOrigSelfSend = pb.oldSelfFlag;
- }
-
-
- /*
- * restores AppleTalk option to talk to one's own node. ONLY for SE's, //'s or MacPluses with AppleTalk driver of v48 or greater!!
- * uses value in the global gOrigSelfSend.
- */
- void restoreSetSelfSend()
- {
-
- SetSelfparms pb;
-
- pb.newSelfFlag = gOrigSelfSend; /* set self send option to saved value*/
- PSetSelfSend((MPPPBPtr) &pb, false);
- }
-
-
- /*
- * Checks to see if we are running AppleTalk Phase 2 compatible drivers.
- */
- void phase2Check()
- {
- if(GMAC.atDrvrVersNum >= 53)
- gHasPhase2 = true;
- else
- HideDialogItem(gLookupDialog, kPhase2Item);
- }
-
-
- /*
- * Opens up AppleTalk. Opens our ATP socket. Initializes our flag
- * which indicate the current state of AppleTalk. If AppleTalk is not
- * open, then we do not want to display the zone list.
- */
- void InitAppleTalkVars()
- {
- extern void getTheZoneList();
- OSErr err;
-
- /*
- * buffer necessary for async name lookups
- * this routine can be called from the TransQueue
- */
- if (gPBLkUP == nil)
- gPBLkUP = (myMPPParamBlock *) NewPtr(sizeof(myMPPParamBlock));
- if (gBuffPtr == nil)
- gBuffPtr = NewPtr(kLookupBufSize);
- gMyNTE.nt.nteAddress.aSocket = kEchoSocket;
-
- if ((gPBLkUP == nil) || (gBuffPtr == nil))
- BigBadError("\pError allocating lookup memory - Aborting program");
- else
- {
- if (IsMPPOpen())
- {
- ((dmzEntryPtr) *(gATQEntry.globs))->atalkActive = true;
- ((dmzEntryPtr) *(gATQEntry.globs))->atalkStatusChanged = false;
- ((dmzEntryPtr) *(gATQEntry.globs))->dmzNTEPtr = nil;
- if (ActivateOpenTransport() != noErr) //
- phase2Check();
- enableSetSelfSend();
- getTheZoneList();
- registerMyName();
-
- /* call socket listener init code */
- err = InitEchoBuffers();
- if (err != noErr)
- {
- BigBadError("\pError initializing Echo Buffers");
- }
- }
- else
- {
- ((dmzEntryPtr) *(gATQEntry.globs))->atalkActive = false;
- ((dmzEntryPtr) *(gATQEntry.globs))->atalkStatusChanged = false;
- ((dmzEntryPtr) *(gATQEntry.globs))->dmzNTEPtr = nil;
- tellUserNoZones(); // which tells the user that AppleTalk is off
- }
-
- }
- }
-
-
-
- /*
- * in order for us to use the standard qsort() algorithm, our data must be alligned in
- * an orderly fashion with a set offset from each data entry. This routine takes care of
- * that through simple _BlockMove manipulations.
- */
- void addToUnpackedBuffer(Ptr oldBuffer, Ptr newBuffer, short numGot, short total)
- {
- long oldIndex = 0L, newIndex = 0L;
- short i;
-
- for(i=0;i<numGot;i++) {
- if (((newIndex + total) * 33) > (kMaxZoneBuffSize - 32))
- break; // protect against potentially writing beyond the buffer
-
- BlockMove((Ptr)oldBuffer+oldIndex, (Ptr)newBuffer+(newIndex+total)*33, 33L);
- oldIndex += (char)((Ptr)oldBuffer+oldIndex)[0]+1L;
- newIndex += 1;
- }
- }
-
-
- /*
- * return our local zone name the old fashioned way. We could easily use the
- * GetMyZone function, which would be simpler
- */
- void getMyZone(char *myZoneBuffer)
- {
- BDSElement myZoneBDS;
- ATPParamBlock ZonePB;
-
- // check whether Open Transport is active and use it to get MyZone
- if (OpenTransportActive())
- {
- DoOTGetMyZone(myZoneBuffer);
- }
- else
- {
- myZoneBDS.buffSize = 33;
- myZoneBDS.buffPtr = (Ptr) myZoneBuffer;
- myZoneBDS.dataSize = 0;
- myZoneBDS.userBytes = 0;
-
- ZonePB.ATPatpFlags = 0;
- ZonePB.ATPioCompletion = 0L;
- ZonePB.ATPuserData = 0; /* ATP user data */
- ZonePB.ATPaddrBlock = gTheBridgeAddress;
- ZonePB.ATPreqLength = 0;
- ZonePB.ATPreqPointer = 0L;
- ZonePB.ATPbdsPointer = (Ptr)&myZoneBDS;
- ZonePB.ATPnumOfBuffs = 1;
- ZonePB.ATPtimeOutVal = 3;
- ZonePB.ATPretryCount = 3;
-
- /*
- * make sure to NIL this field out so bottom three bytes are 0
- */
- ZonePB.ATPuserData = 0x07000000; /* GetLocalZone = 7 */
-
- if(PSendRequest(&ZonePB, false) != noErr)
- myZoneBuffer[0] = 0;
- }
- }
-
-
- void doGetZoneListPrePh2()
- {
- BDSElement myZoneBDS;
- ATPParamBlock ZonePB;
- OSErr theResult;
- long tempUserData;
- Ptr theBufferPtr;
- short zIndex, zoneCallType;
- short NumZonesGot = 0, totalZones = 0;
- Boolean DontGetMoreZones;
- extern ListHandle zonesList;
- Ptr returnBuffer;
-
- zIndex = 1;
- zoneCallType = _GetZoneList;
- DontGetMoreZones = false;
-
- returnBuffer = NewPtr(kMaxZoneBuffSize); /* set to max SInt16 */
-
- theBufferPtr = NewPtr(578); /* size of BDS */
- if(MemError()==noErr) {
- while(!DontGetMoreZones) {
- zIndex += NumZonesGot; /* index count. 1 for start */
- myZoneBDS.buffSize = 578;
- myZoneBDS.buffPtr = theBufferPtr;
- myZoneBDS.dataSize = 0;
- myZoneBDS.userBytes = 0;
-
- ZonePB.ATPatpFlags = 0;
- ZonePB.ATPioCompletion = 0L;
- ZonePB.ATPuserData = 0; /* ATP user data */
- ZonePB.ATPaddrBlock = gTheBridgeAddress;
- ZonePB.ATPreqLength = 0;
- ZonePB.ATPreqPointer = 0L;
- ZonePB.ATPbdsPointer = (Ptr)&myZoneBDS;
- ZonePB.ATPnumOfBuffs = 1;
- ZonePB.ATPtimeOutVal = 4;
- ZonePB.ATPretryCount = 4;
-
- BlockMove((Ptr) &zoneCallType + 1, (Ptr) &tempUserData, 1L);
- BlockMove((Ptr) &zIndex, (Ptr)&tempUserData + 2, 2L);
-
- ZonePB.ATPuserData = tempUserData;
-
- theResult = PSendRequest(&ZonePB, false);
-
- if(theResult == noErr) {
- tempUserData = myZoneBDS.userBytes;
- BlockMove((Ptr) &tempUserData, (Ptr) &DontGetMoreZones, 1); /* the highbyte will be nonzero if its the last packet of zones */
- BlockMove((Ptr)&tempUserData + 2, (Ptr) &NumZonesGot, 2);
-
- addToUnpackedBuffer(myZoneBDS.buffPtr, returnBuffer, NumZonesGot, totalZones);
-
- totalZones += NumZonesGot;
- }
- }
-
- SetZoneCells(returnBuffer, totalZones);
-
- DisposePtr(theBufferPtr);
- DisposePtr(returnBuffer);
- }
-
- }
-
- /*
- * zonesPresent is used to determine whether zones are present by checking the
- * existence of a router. In previous releases, we use to check that the
- * network number was non-zero. Under ARA, the network number could be zero
- * however, the bridge node ID might not be. This correction was implemented
- * by Pete Lovell, GE Information Services
- */
- Boolean zonesPresent()
- {
- short theBridgeNode = 0;
- short theBridgeNet = 0;
- short node;
- OSErr err;
-
- if (!OpenTransportActive())
- { // open transport is not active - do things the traditional method
- err = GetNodeAddress(&node, &theBridgeNet);
- /*
- * On an extended network, this node ID is simply a flag. Use _GetAppletalkInfo to get the
- * real 24 bit address of the last router heard from.
- */
- theBridgeNode = GetBridgeAddress();
-
- if (theBridgeNode != 0)
- {
- gTheBridgeAddress.aNet = theBridgeNet;
- gTheBridgeAddress.aNode = theBridgeNode;
- gTheBridgeAddress.aSocket = kBridgeSocket;
- return true;
- }
- else
- return false;
- }
- else
- { // open transport is active
- GetBridgeAddressFromOT(&gTheBridgeAddress);
- if (gTheBridgeAddress.aNode != 0)
- return true;
- else
- return false;
- }
- }
-
-
- void setItemString(DialogPtr whichDialog, short whichItem, Str255 str)
- {
- Rect r;
- short kind;
- Handle h;
-
- GetDialogItem(whichDialog, whichItem, &kind, &h, &r);
- SetDialogItemText(h, str);
- }
-
-
- /*
- * getTheZoneList is used to call the appropriate method to get the
- * zone list - assuming that zones are present.
- */
- void getTheZoneList()
- {
- StartAnimatedCursors(kSpinEvery5Ticks, 15);
- if (zonesPresent())
- {
- if (OpenTransportActive() == false)
- {
- /*
- * if AppleTalk Phase 2 is present (>= v53) then use new call
- */
- if(gHasPhase2)
- doGetZoneListPhs2();
- else
- doGetZoneListPrePh2();
- }
- else
- DoOTGetZoneList();
- }
- else
- {
- /*
- * no zones. inform user of this.
- */
- tellUserNoZones();
- }
- StopAnimatedCursors();
- }
-
-
- void processListUpdate()
- {
- Str255 tempStr, errorStr;
-
- if (OpenTransportActive())
- {
- ProcessOTListUpdate((char *)tempStr);
- }
- else
- {
- if(gPBLkUP->myMPP.MPPioResult >= noErr)
- {
- NumToString((long) gPBLkUP->myMPP.NBPnumGotten, tempStr);
- Pstrcat(tempStr, "\p items");
-
- SetObjectTypeCells(gBuffPtr, gPBLkUP->myMPP.NBPnumGotten);
- }
- else
- {
- NumToString((long) gPBLkUP->myMPP.MPPioResult, errorStr);
- tempStr[0] = 0;
- Pstrcat(tempStr, "\pErr = ");
- Pstrcat(tempStr, errorStr);
- }
- }
-
- gUpdateListFlag = false;
- gLookupFinished = true;
- StopAnimatedCursors();
-
- /* nil out specified text in dialog box since we're done looking */
- if (OpenTransportActive())
- ParamText("\p", "\p", "\p", "\pOT active");
- else
- ParamText("\p", "\p", "\p", "\p");
-
- setItemString(gMyDialog, (short) kObjectCountID, tempStr);
-
- invalidateItem(kProgressID);
- invalidateItem(kObjectCountID);
- }
-
-
- /*
- * myCompletionRoutine is called to set a global flag which is
- * inspected each time through the event loop. The routine is
- * used by the asynch lookup call. When the lookup completes,
- * the global flag is set telling the program to process the
- * lookup replies - sort them per specified order. For PowerPC
- * there is no need to set the A5 world as the OS does it for you.
- */
-
- #ifdef powerc
- void myCompletionRoutine(ParamBlockRec *paramBlock)
- {
- gUpdateListFlag = true;
- }
- #else
- void myCompletionRoutine(ParamBlockRec *paramBlock)
- {
- #ifndef __MWERKS__
- #pragma unused (paramBlock)
- #endif
-
- saveThatA5();
- gUpdateListFlag = true;
- restoreThatA5();
- }
- #endif
-
- char giveMeItemValue(short whichItem)
- {
- Rect r;
- short kind;
- Handle h;
- Str255 str;
- long value;
-
- GetDialogItem(gLookupDialog, whichItem, &kind, &h, &r);
- GetDialogItemText(h, str);
- StringToNum(str, &value);
-
- if(value>255) {
- value = 255L;
- SetDialogItemText(h, "\p255");
- }
- else if(value<0) {
- value = 0L;
- SetDialogItemText(h, "\p0");
- }
- return (short)value;
- }
-
- void giveMeItemString(short whichItem, Str255 str)
- {
- Rect r;
- short kind;
- Handle h;
-
- GetDialogItem(gLookupDialog, whichItem, &kind, &h, &r);
- GetDialogItemText(h, str);
- }
-
- /*
- * getTypesNamesInZone is called to initiate the NBP lookup
- * request.
- * used by the asynch lookup call. When the lookup completes,
- * the global flag is set telling the program to process the
- * lookup replies - sort them per specified order. For PowerPC
- * there is no need to set the A5 world as the OS does it for you.
- */
- void getTypesNamesInZone(char *NBPZone)
- {
- OSErr resultCode;
- Str255 NBPObject, NBPType;
- Str255 tempText;
- Str32 noZoneName = "\pNo zones <*>.";
- Str32 localZone = "\pthe local zone";
- Boolean localFlag = false;
- static MPPCompletionUPP gMyCompletionRoutineUPP = nil;
-
- if (((dmzEntryPtr) *(gATQEntry.globs))->atalkActive == false) // ATalk not active.
- return;
-
- /*
- * Check whether there are no zones in the zone list
- */
- if (PStrComp(noZoneName, (unsigned char *)gNameGlob))
- localFlag = true;
-
- giveMeItemString(kObjectItem, NBPObject);
- giveMeItemString(kTypeItem, NBPType);
- BlockMove(NBPZone, &gNameGlob[0], sizeof(gNameGlob));
-
- if (OpenTransportActive() == true)
- {
- DoOTNameLookup((char *)NBPObject, (char *)NBPType, (char *)NBPZone);
- }
- else
- {
- StartAnimatedCursors(kSpinEvery5Ticks, 15);
- if (gMyCompletionRoutineUPP==nil)
- gMyCompletionRoutineUPP = NewMPPCompletionProc(myCompletionRoutine);
-
- /*
- * oh dang... there may be an NBPLookup already pending. Kill It first.
- */
- killLookups();
-
- NBPSetEntity((Ptr)&gLookupNTE.nt.entityData[0], (ConstStr32Param)NBPObject,
- (ConstStr32Param)NBPType, (ConstStr32Param)NBPZone);
-
- gPBLkUP->myA5 = (long)LMGetCurrentA5(); /* get the Current A5 */
-
- gLookupFinished = false;
-
- gPBLkUP->myMPP.MPPioCompletion = gMyCompletionRoutineUPP;
- gPBLkUP->myMPP.NBPinterval = giveMeItemValue(kIntervalItem);
- gPBLkUP->myMPP.NBPcount = giveMeItemValue(kCountItem);
- gPBLkUP->myMPP.NBPentityPtr = (Ptr)&gLookupNTE.nt.entityData;
- gPBLkUP->myMPP.NBPretBuffSize = kLookupBufSize;
- gPBLkUP->myMPP.NBPretBuffPtr = (Ptr) gBuffPtr;
- gPBLkUP->myMPP.NBPmaxToGet = kLookupBufSize / kNBPEntityBufferSize;
-
- resultCode = PLookupName((MPPParamBlock *) &gPBLkUP->myMPP, true);
- if (resultCode == 0)
- {
- gLookupFinished = true;
- StopAnimatedCursors();
- }
- }
-
- /*
- * inform the user of what we are doing
- * and zero out current entity count.
- */
- tempText[0] = 0;
- if (localFlag)
- Pstrcat(tempText, localZone);
- else
- Pstrcat(tempText, (unsigned char *)NBPZone);
-
- Pstrcat(tempText, "\p…");
- ParamText("\p", "\p", "\plooking in:", tempText);
-
- tempText[0] = 0;
- setItemString(gMyDialog, (short) kObjectCountID, tempText);
-
- invalidateItem(kProgressID);
- invalidateItem(kObjectCountID);
-
- }
-
-
- /*
- * GetMyZone function
- */
- void doGetMyZonePhs2()
- {
- XCallParam xpb;
- OSErr resultCode;
- char myZoneNameBuffer[33];
- short refNum;
-
- resultCode = OpenDriver("\p.XPP", &refNum);
-
- xpb.ioRefNum = refNum;
- xpb.csCode = xCall;
- xpb.xppSubCode = zipGetMyZone;
- xpb.zipBuffPtr = (Ptr) &myZoneNameBuffer;
- xpb.zipInfoField[0] = 0; /* ALWAYS 0 */
- resultCode = PBControl((ParmBlkPtr) &xpb, false);
- }
-
- void doGetLocalZonesPhs2()
- {
- XCallParam xpb;
- OSErr resultCode = 0;
- Ptr returnBuffer, theBufferPtr;
- short refNum;
- short totalZones = 0;
-
- resultCode = OpenDriver("\p.XPP", &refNum);
-
- returnBuffer = NewPtr(kMaxZoneBuffSize); /* set to max SInt16 */
-
- theBufferPtr = NewPtr(578); /* size of BDS */
- if(MemError()==noErr) {
-
- xpb.zipInfoField[0] = 0; /* ALWAYS 0 on first call. has state info on subsequent calls */
- xpb.zipLastFlag = 0;
-
- xpb.ioRefNum = refNum;
- xpb.csCode = xCall;
- xpb.xppSubCode = zipGetLocalZones;
- xpb.xppTimeout = 3;
- xpb.xppRetry = 4;
- xpb.zipBuffPtr = (Ptr) theBufferPtr;
-
- while(xpb.zipLastFlag == 0 && resultCode == 0) {
-
- resultCode = PBControl((ParmBlkPtr) &xpb, false);
-
- if(resultCode == noErr) {
- SpinTheCursor();
- addToUnpackedBuffer(theBufferPtr, returnBuffer, xpb.zipNumZones, totalZones);
- totalZones += xpb.zipNumZones;
- }
- }
-
- if(resultCode == noErr)
- SetZoneCells(returnBuffer, totalZones);
-
- DisposePtr(theBufferPtr);
- DisposePtr(returnBuffer);
- }
- }
-
- /*
- * When AppleTalk Phase 2 is present, things go a bit easier.
- */
- void doGetZoneListPhs2()
- {
- XCallParam xpb;
- OSErr resultCode = 0;
- Ptr returnBuffer, theBufferPtr;
- short refNum;
- short totalZones = 0;
-
- resultCode = OpenDriver("\p.XPP", &refNum);
-
- returnBuffer = NewPtr(kMaxZoneBuffSize); /* set to max SInt16 */
-
- theBufferPtr = NewPtr(578); /* size of BDS */
-
- if(MemError()==noErr) {
- xpb.zipInfoField[0] = 0; /* ALWAYS 0 on first call. has state info on subsequent calls */
- xpb.zipInfoField[1] = 0; /* ALWAYS 0 on first call. has state info on subsequent calls */
- xpb.zipLastFlag = 0;
-
- xpb.ioRefNum = refNum;
- xpb.csCode = xCall;
- xpb.xppSubCode = zipGetZoneList;
- xpb.xppTimeout = 3;
- xpb.xppRetry = 4;
- xpb.zipBuffPtr = (Ptr) theBufferPtr;
-
- while(xpb.zipLastFlag == 0 && resultCode == 0) {
- resultCode = PBControl((ParmBlkPtr) &xpb, false);
-
- if(resultCode == noErr) {
- SpinTheCursor();
- addToUnpackedBuffer(theBufferPtr, returnBuffer, xpb.zipNumZones, totalZones);
- totalZones += xpb.zipNumZones;
- }
- }
- /*
- * If all went well, add zone names to our list.
- */
- if(resultCode == noErr)
- SetZoneCells(returnBuffer, totalZones);
-
- /*
- * Dispose of memory we allocated.
- */
- DisposePtr(theBufferPtr);
- DisposePtr(returnBuffer);
- }
- }
-
- /*
- * setupEchoDialog displays the echo packet test results having
- * processed the return packet. This dialog displays the results
- * in terms of hop count to reach the object and seconds required to
- * "ping" the object. If an error occurred, it is displayed instead
- */
- void setupEchoDialog(DialogPtr echoDialog, myNetworkEntity *myEnt)
- {
- short kind;
- Handle h;
- Rect r;
- Str32 noZoneName = "\pNo zones <*>.";
- Str32 localZone = "\plocal zone";
- Boolean localFlag = false;
- static UserItemUPP gAboutOKFrameUPP = nil;
-
- if (gAboutOKFrameUPP==nil)
- gAboutOKFrameUPP = NewUserItemProc(aboutDialogOKFrame);
-
- GetDialogItem(echoDialog, 10, &kind, &h, &r);
- SetDialogItemText(h, (ConstStr255Param)myEnt->object);
-
- GetDialogItem(echoDialog, 11, &kind, &h, &r);
- SetDialogItemText(h, (ConstStr255Param)myEnt->type);
-
- GetDialogItem(echoDialog, 12, &kind, &h, &r);
- if (PStrComp(noZoneName, (unsigned char *)gNameGlob))
- SetDialogItemText(h, localZone);
- else
- SetDialogItemText(h, (ConstStr255Param)gNameGlob);
-
- /*
- * set up the userItem proc for the "OK" button outline
- */
- GetDialogItem(echoDialog, 13, &kind, &h, &r);
- SetDialogItem(echoDialog, 13, userItem, (Handle) gAboutOKFrameUPP, &r);
- }
-
-
- /*
- * doEcho is called when the user double clicks on some item indicating
- * to send an echo packet to the echo socket on the node of that item.
- * Note all of the preparation which is performed in order to "ping" the
- * object. Note that the socket listener code has been implemented as
- * a code resource so that for PowerPC we can make a mixed mode call to it.
-
- */
- void doEcho(myNetworkEntity *myEnt)
- {
- MPPParamBlock myMPP;
- OSErr err;
- Boolean gotEcho = false;
- WDSElement myWDS[3]; /* minimum of 3 WDS elements in a Write Data Structure */
- Ptr gHdrPtr;
- Ptr myBuffer;
- long myTicks, myWaitTicks, startTicks, stopTicks;
- unsigned char myHops;
- DialogPtr echoDialog;
- Str255 str;
- short kind;
- Handle h;
- Rect r;
- short itemHit;
- AddrBlock destAddress;
- long tempL;
- GrafPtr savedPort;
- PacketPtr bufPtr;
-
- GetPort(&savedPort);
-
- StartAnimatedCursors(kSpinEvery5Ticks, 15);
-
- StringToNum((StringPtr) myEnt->net, (long *) &tempL);
- destAddress.aNet = tempL;
- StringToNum((StringPtr) myEnt->node, (long *) &tempL);
- destAddress.aNode = tempL;
- StringToNum((StringPtr) myEnt->socket, (long *) &tempL);
- destAddress.aSocket = tempL;
-
- echoDialog = GetNewDialog(131, 0L, (WindowPtr) -1L);
- SetPort(echoDialog);
-
- TextFont(geneva);
- TextSize(9);
-
- setupEchoDialog(echoDialog, myEnt);
-
- myMPP.DDPlistener = (DDPSocketListenerUPP) *gSockCodeHndl;
-
- myMPP.DDPsocket = 0;
- err = POpenSkt(&myMPP, false);
-
- gHdrPtr = NewPtr(17); /* max header size */
-
- destAddress.aSocket = 4; /* Echoer socket */
- myBuffer = NewPtr(ddpMaxData);
- *myBuffer = 1; /* tell their Echoer we want a reply with a 1 in the first byte */
-
- BuildDDPwds((Ptr) &myWDS, gHdrPtr, myBuffer, destAddress, kEchoSocket, ddpMaxData);
-
- myMPP.DDPchecksumFlag = true;
- myMPP.DDPwdsPointer = (Ptr) &myWDS;
-
- startTicks = TickCount(); /* start the timer! */
-
- err = PWriteDDP(&myMPP, false);
-
- myWaitTicks = TickCount() + 600L; /* wait 10 seconds for reply */
-
- while(myWaitTicks > TickCount() && !gUsedQ.qHead)
- {
- SpinTheCursor();
- }
-
- if(gUsedQ.qHead) {
- bufPtr = (PacketPtr)gUsedQ.qHead; /* get the packet ptr */
- /* we could check the DDP type in the buffer_type field
- * but we leave it as an exercise to the reader.
- * Note that the way the gUsedQ is structured so that
- * we could check whether the packet is for us, or for
- * some other process which utilizes the same listener.
- * In the next step we dequeue the packet so that it
- * doesn't get overwritten */
- if (Dequeue((QElemPtr)gUsedQ.qHead, &gUsedQ) == noErr) {
- if (bufPtr->buffer_CheckSum != noErr)
- {
- GetDialogItem(echoDialog, 6, &kind, &h, &r);
- SetDialogItemText(h, "\pWah…Checksum error occurred");
- }
- else
- {
- stopTicks = bufPtr->buffer_Ticks;
- myTicks = stopTicks - startTicks;
-
- GetDialogItem(echoDialog, 4, &kind, &h, &r);
- myHops = bufPtr->buffer_Hops;
- NumToString((long) myHops, (void *) &str);
- SetDialogItemText(h, str);
-
- GetDialogItem(echoDialog, 5, &kind, &h, &r);
- NumToString(myTicks, (void *) &str);
- SetDialogItemText(h, str);
- }
- /* requeue the packet buffer for use. */
- Enqueue((QElemPtr)bufPtr, &gFreeQ);
- }
- else {
- GetDialogItem(echoDialog, 6, &kind, &h, &r);
- SetDialogItemText(h, "\pWah… packet Dequeue error occured");
- }
- }
- else {
- GetDialogItem(echoDialog, 6, &kind, &h, &r);
- SetDialogItemText(h, "\pWah… no echo reply received!");
- }
- /* clean up memory allocations */
- DisposePtr(gHdrPtr);
- DisposePtr(myBuffer);
- err = PCloseSkt(&myMPP, false);
-
- /* report the results */
- centerDialog((WindowPtr) echoDialog);
-
- StopAnimatedCursors();
-
- InitCursor();
- ShowWindow(echoDialog);
-
- ModalDialog(0L, &itemHit);
- DisposeDialog(echoDialog);
-
- SetPort(savedPort);
- }
-
-
- /*
- * Here's our AppleTalk Transition Queue handler - we just want
- * to know if the user shuts down AppleTalk, or changes connections
- * and do the right thing like deregister our NBP name. On entry
- * the current A5 world gets saved under 68K and set to that of
- * our application. We can then make calls to the program and
- * use program globals.
- */
-
- long ATalkTransQueue(long selector, myATQEntry *q, void *p)
- {
- #pragma unused (p)
- long returnVal = 0; /* return 0 for unrecognized events */
- dmzEntryPtr dmzPtr;
- long a5Save;
-
- //DebugStr("\pEntering ATQ");
-
- #ifndef powerc
- /* set a5 to that for the app */
- a5Save = SetA5(q->myA5);
- #endif
- /*
- * This is the dispatch part of the routine. We'll check the selector passed into
- * the task; its location is 4 bytes off the stack (selector).
- */
-
- dmzPtr = (dmzEntryPtr)*(q->globs);
- switch(selector) {
- case ATTransOpen:
- /*
- * Someone has opened the .MPP driver. Set Flag to re-initialize AppleTalk portion of pgm
- */
-
- dmzPtr->atalkStatusChanged = true;
- dmzPtr->atalkActive = true;
- break;
-
- case ATTransClose:
- /*
- * .MPP is going to shut down no matter what we do. Call Cleanup routine
- */
-
- removeMyNameAndSocket();
-
- dmzPtr->atalkStatusChanged = true;
- dmzPtr->atalkActive = false;
- break;
-
-
- case ATTransClosePrep:
- /*
- * .MPP is asking whether it can shut down.
- */
-
- break;
-
- } /* end of switch */
-
- /*
- * return value in register D0
- */
- #ifndef powerc
- SetA5(a5Save);
- #endif
- return returnVal;
- }
-
- /*
- * This routine loads the socket listener code and initializes the buffers to
- * be used by the socket listener code. A check is made to determine whether VM
- * is active and to hold the memory associated with buffers that might be
- * critical to the operation of the socket listener. We load the socket
- * socket listener code resource and lock it in memory.
- */
-
- OSErr InitEchoBuffers(void)
- {
- OSErr err = noErr;
- short i;
- Size listenerSize;
-
- /* check whether the buffers have already been init'd */
-
- if (!(TstSocketBuffsInitdFlag(gATalkFlags))) {
- /* set up the free and used queues */
- gFreeQ.qFlags = 0;
- gFreeQ.qHead = nil;
- gFreeQ.qTail = nil;
-
- gUsedQ.qFlags = 0;
- gUsedQ.qHead = nil;
- gUsedQ.qTail = nil;
-
- /* enqueue the packet buffer records to the free queue */
- for (i=0; i<kNumBuffers; i++, gFreeQ.qFlags ++)
- Enqueue((QElemPtr)&gBuffers[i], &gFreeQ);
-
- /* show that the buffers have been init'd */
- SetSocketBuffsInitdFlag(gATalkFlags);
-
- /* check whether VM is on and hold the packet buffers */
- if (TstVMActiveFlag(gATalkFlags))
- {
-
- err = HoldMemory(&gBuffers, sizeof(gBuffers));
- if (err == noErr) {
- /* mark queue structures for hold */
- HoldMemory(&gFreeQ, sizeof(QHdr));
- HoldMemory(&gUsedQ, sizeof(QHdr));
- /* set the global ATalkFlags to reflect the held memory */
- SetSocketBuffsHeldFlag(gATalkFlags);
- }
- }
-
- /*********** get socket listener code **********/
- if ((gSockCodeHndl == nil) && (OpenTransportActive() == false))
- {
- gSockCodeHndl = Get1Resource('Sock',128);
- if (gSockCodeHndl==nil)
- return (resNotFound);
- MoveHHi(gSockCodeHndl);
- HLock(gSockCodeHndl);
-
- /* tell the socket listener about the 2 queues */
- err = CallInitSktListenerProc(((InitSktListenerProcPtr)((long) *gSockCodeHndl + 2)), &gFreeQ, &gUsedQ);
-
- /*********** end get socket listener code **********/
-
- if (err == noErr) {
- if (TstVMActiveFlag(gATalkFlags))
- {
- listenerSize = GetHandleSize(gSockCodeHndl);
-
- err = HoldMemory(*gSockCodeHndl, listenerSize);
- if (err == noErr)
- SetListenerHeldFlag(gATalkFlags);
- }
- }
- if (err)
- BigBadError("\pSocket listener init failed - aborting program");
- /* I guess we could fail the use of the socket listener
- * instead of aborting the program however, that is left as an
- * exercise to the user
- */
- }
-
- }
- return(err);
-
- }
-
- Boolean GestaltAvailable(void)
- {
- return (TrapAvailable(_Gestalt));
- }
-
-
- short AppleTalkVersion(void)
- {
- short versionRequested = 1; /* version of SysEnvRec */
- short refNum;
- long attrib;
- short atlkVer;
-
- atlkVer = 0; /* default to no AppleTalk */
- if (GestaltAvailable()) /* check whether Gestalt is available */
- {
- if (Gestalt('atkv', &attrib) == noErr) /* check the atkv selector which */
- { /* return ATalk version regardless whether */
- /* ATalk is on or off */
- atlkVer = attrib >> 24;
- }
- else if (OpenDriver("\p.MPP", &refNum) == noErr) /* open, then check the 'atlk' */
- { /* selector to get ATalk version */
- if (Gestalt(gestaltAppleTalkVersion, &attrib) == noErr)
- atlkVer = attrib & 0x000000FF;
- }
- }
- return atlkVer;
- }
-
-
- Boolean LAPMgrExists(void)
- {
- return (AppleTalkVersion() >= 53);
- }
-